package cn.py.boot_lua.asyn.updateAsyncMeth;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.DisposableBean;
import org.springframework.stereotype.Component;

import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.function.Consumer;
import java.util.concurrent.Executor;

@Component
public class AsyncTaskManager implements DisposableBean {

    private static final Logger log = LoggerFactory.getLogger(AsyncTaskManager.class);

    private final Map<String, AsyncQueueTaskEngine<?>> engines = new ConcurrentHashMap<>();

    private final Map<String, Executor> executorMap;

    public AsyncTaskManager(Map<String, Executor> executorMap) {
        this.executorMap = executorMap;
        log.info("AsyncTaskManager 初始化，发现 {} 个 Executor Bean", executorMap.size());
    }

    /**
     * 提交异步任务
     */
    @SuppressWarnings("unchecked")
    public <T> boolean submit(String queueName,
                              T taskData,
                              String executorBeanName,
                              int maxConcurrency,
                              Consumer<T> handler) {

        AsyncQueueTaskEngine<T> engine = (AsyncQueueTaskEngine<T>) engines.computeIfAbsent(queueName, name -> {
            Executor executor = executorMap.get(executorBeanName);
            if (executor == null) {
                throw new IllegalArgumentException("未找到 Executor Bean: " + executorBeanName);
            }
            log.info("创建新的队列 [{}] 使用线程池 [{}]", name, executorBeanName);
            return new AsyncQueueTaskEngine<>(name, executor, maxConcurrency, handler);
        });
        return engine.submitTask(taskData);
    }

    /**
     * 自定义配置提交（支持错误处理器、队列容量）
     */
    @SuppressWarnings("unchecked")
    public <T> boolean submit(String queueName,
                              T taskData,
                              String executorBeanName,
                              int maxConcurrency,
                              Consumer<T> handler,
                              Consumer<Exception> errorHandler,
                              int queueCapacity) {

        AsyncQueueTaskEngine<T> engine = (AsyncQueueTaskEngine<T>) engines.computeIfAbsent(queueName, name -> {
            Executor executor = executorMap.get(executorBeanName);
            if (executor == null) {
                throw new IllegalArgumentException("未找到 Executor Bean: " + executorBeanName);
            }
            log.info("创建新的队列 [{}] 使用线程池 [{}], queueCapacity={}", name, executorBeanName, queueCapacity);
            return new AsyncQueueTaskEngine<>(name, executor, maxConcurrency, handler, errorHandler, queueCapacity);
        });

        return engine.submitTask(taskData);
    }

    /**
     * Spring 容器关闭时自动调用
     */
    @Override
    public void destroy() {
        log.info("AsyncTaskManager 正在关闭所有队列引擎...");
        engines.values().forEach(AsyncQueueTaskEngine::shutdown);
        log.info("AsyncTaskManager 已关闭");
    }

    // ---测试 -> 监控用 ---
    public Map<String, EngineStatus> getStatus() {
        Map<String, EngineStatus> status = new ConcurrentHashMap<>();
        engines.forEach((name, engine) -> {
            status.put(name, new EngineStatus(
                    engine.getQueueSize(),
                    engine.getRemainingCapacity(),
                    engine.getActivePermits(),
                    engine.isRunning()
            ));
        });
        return status;
    }

    public static class EngineStatus {
        public final int queueSize;
        public final int remainingCapacity;
        public final int activePermits;
        public final boolean running;

        public EngineStatus(int queueSize, int remainingCapacity, int activePermits, boolean running) {
            this.queueSize = queueSize;
            this.remainingCapacity = remainingCapacity;
            this.activePermits = activePermits;
            this.running = running;
        }
    }

}
